package com.woniuxy.woniubook.controller;


import com.google.code.kaptcha.Producer;
import com.woniuxy.woniubook.entity.User;
import com.woniuxy.woniubook.service.UserService;
import com.woniuxy.woniubook.uitl.CookieUtil;
import com.woniuxy.woniubook.uitl.JwtUtils;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.mail.SimpleMailMessage;
import org.springframework.mail.javamail.JavaMailSender;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;


import javax.imageio.ImageIO;
import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.awt.image.BufferedImage;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.Map;
import java.util.Random;
import java.util.concurrent.TimeUnit;

/**
 * <p>
 *  前端控制器
 * </p>
 *
 * @author wugd
 * @since 2022-11-16 02:13:12
 */
@Controller
@RequestMapping("/user")
public class UserController {

    @Autowired
    UserService userService ;
    @Autowired
    Producer producer ;

    @Autowired
    RedisTemplate<String,Object> redisTemplate ;

    @Autowired
    JavaMailSender javaMailSender ;

    @Autowired
    RabbitTemplate rabbitTemplate ;

    @Value("${fromEmail}")
    private String fromEmail ;

    @RequestMapping("/login")
    public String login(String username , String password, String code, Map map,
                        HttpServletRequest request, HttpServletResponse response) throws IOException {
        //验证验证码
        String imgCode = "0000" ;//(String) request.getSession().getAttribute("kapatchaStr");
        if (code == null || !code.equals(imgCode)) {
            map.put("errorInfo","验证码错误!");
            return "login" ;
        }
        User user = userService.getUserByName(username);
        if(user == null) {
            map.put("errorInfo","账户不存在!");
            return "login" ;
        }else {
            if(user.getPassword().equals(password)) {
                //登录成功
                //session.setAttribute("userInfo",user);
                // 登录成功之后  创建一个 token
                String token = JwtUtils.createToken(user.getAccount(),15);
                //把token 写到 客户端   利用Cookie
                CookieUtil.addCookie(request,response,token);
                // 在redis 存储一 token 时间设置是 token 过期时间的2倍
                String token1 = JwtUtils.createToken(user.getAccount(),30);
                redisTemplate.opsForValue().set(user.getAccount()+"_user_token",token1,30*60, TimeUnit.SECONDS);

                //把当前用户名存储到 redis 键值是 token
                redisTemplate.opsForValue().set(token,user.getAccount());

                return "redirect:/" ;
            }else {
                map.put("errorInfo","密码错误!");
                return "login" ;
            }
        }
    }

    /**
     * 获得生成的随机验证码
     * @param response
     * @param httpSession
     */
    @GetMapping("/login/getKapatchaImage")
    public void getKapatchaImage(HttpServletResponse response, HttpSession httpSession){
        //生成验证码
        String text = producer.createText();
        BufferedImage image = producer.createImage(text);

        //验证码字符串写入到session中.服务器将依托cookie 【key,value】value中存放的是当前生成的sessionid.
        //以后浏览器访问浏览器时，将会携带该cookie信息，使得多个浏览器请求中携带重要的信息【基于HTTP请求是无状态的，将验证字符串存入到session中，保存到服务中】
        httpSession.setAttribute("kapatchaStr", text);
        //存储到redis ???   生成一个唯一的键   把键 存储到客户端   Cookie

        //图片响应给response
        //响应格式为.png的图片
        response.setContentType("image/png"); //text/html
        //PrintWriter writer = response.getWriter();
        try {
            ServletOutputStream outputStream = response.getOutputStream();
            //响应给浏览器的是验证码图片
            ImageIO.write(image,"png",outputStream);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }


    @RequestMapping("/getAccount")
    @ResponseBody
    public String getAccount(HttpServletRequest request){
        String user_token = CookieUtil.getToken(request, "user_token");
        if (user_token == null){
            return "" ;
        }else {
            String account = JwtUtils.getAccount(user_token);
            return account ;
        }
    }

    @RequestMapping("/sendEmail")
    @ResponseBody
    public String sendEmail(String email){
        /*SimpleMailMessage s = new SimpleMailMessage();
        s.setFrom(fromEmail);
        s.setSubject("邮箱验证码");

        String random = Math.random() + "";
        random = random.substring(2,6);

        s.setText(random);
        s.setTo(email);

        javaMailSender.send(s);
        //验证码存储到 redis
        redisTemplate.opsForValue().set(email,random,300 ,TimeUnit.SECONDS);
        System.out.println("emailCode=============================>"+random);*/
        rabbitTemplate.convertAndSend("sendEmailExchange","sendEmail",email);

        return  "ok" ;
    }

    @RequestMapping("/reg")
    @ResponseBody
    public String reg(String account,String password,String repass ,String email,String emailCode){
        if (!repass.equals(password)) {
            return "密码和验证密码不一致" ;
        }
        String code= redisTemplate.opsForValue().get(email)+"";
        if(!emailCode.equals(code)) {
            return "验证码错误!" ;
        }

        //验证用户是否唯一
        User user = userService.getUserByName(account);
        if(user != null) {
            return  "此用户名已经被使用" ;
        }
        //验证邮箱是否唯一
        User userByEmail = userService.getUserByEmail(email);
        if(userByEmail != null){
            return  "邮箱已经被注册，不能使用";
        }
        //如果两个相同账户 ，只允许一个账户执行
        synchronized (account.intern()){
            userService.reg(account,password,email);
        }

        return "ok" ;
    }

}

